package cn.edu.zut.sunday.boolq.service.impl;

import cn.edu.zut.sunday.boolq.dao.BoolqInfoRepository;
import cn.edu.zut.sunday.boolq.domain.BoolqInfo;
import cn.edu.zut.sunday.boolq.service.ImportBoolqDataService;
import cn.edu.zut.sunday.constant.BoolqDatasetInfo;
import cn.edu.zut.sunday.utils.ReloadFileUtils;
import com.google.gson.Gson;
import java.io.File;
import java.io.IOException;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

@Slf4j
@Service
public class ImportBoolqDataServiceImpl implements ImportBoolqDataService {

    private BoolqInfoRepository boolqInfoRepositoryImpl;

    @Autowired
    public void setBoolqInfoService(BoolqInfoRepository boolqInfoRepositoryImpl) {
        this.boolqInfoRepositoryImpl = boolqInfoRepositoryImpl;
    }

    private static final Gson GSON = new Gson();

    /**
     * 用来读取数据集文件，加载该文件数据（json格式）写入到数据库中
     *
     * @return  是否操作成功
     */
    @Override
    public boolean initDatabase() {
        try {
            List<File> files = ReloadFileUtils.getFiles(BoolqDatasetInfo.DATASET_FILE_PATH);
            // 没有文件则直接返回，不执行加载数据操作
            if (files.size() == 0) {
                return true;
            }
            // 清空数据库
            boolqInfoRepositoryImpl.deleteAll();
            // 处理文件信息
            files.stream()
              // 过滤相关后缀名文件
              .filter(file -> file.getName().endsWith(BoolqDatasetInfo.DATASET_FILE_SUFFIX))
              //读取每一个文件并保存到数据库中
              .forEach(file -> {
                  try {
                      final List<String> lines = ReloadFileUtils.readFileAllLines(file);

                      //每一行都是一个对象，反序列化成对象
                      final List<BoolqInfo> boolqInfoList = lines.stream()
                        .map(line -> GSON.fromJson(line, BoolqInfo.class))
                        .peek(entity -> {
                            //设置时间
                            entity.setDateCreated(new Date());
                            entity.setDateModified(new Date());
                            //处理passage属性过长，这里进行截断
                            entity.setPassage(entity.getPassage()
                              .substring(0, Math.min(512, entity.getPassage().length())));
                        })
                        .collect(Collectors.toList());
                      //把这个文件存入数据库中并立即写入
                      boolqInfoRepositoryImpl.saveAllAndFlush(boolqInfoList);
                  } catch (IOException e) {
                      log.error("read dataset failed. path is: [ {} ], error: {}",
                        file.getName(), e.getMessage());
                  }
              });
            return true;
        } catch (Exception e) {
            log.error("read dataset failed. path is: [ {} ], error: {}",
              BoolqDatasetInfo.DATASET_FILE_PATH, e.getMessage());
        }
        return false;
    }

    @Override
    public String datasetName() {
        return BoolqDatasetInfo.DATASET_NAME;
    }
}
